package com.collect.senegal.zhiBase;

import android.content.Context;
import android.net.ParseException;
import android.text.TextUtils;
import android.util.Log;

import com.collect.senegal.MyApplication;
import com.collect.senegal.R;
import com.collect.senegal.zhiGlobal.zhiAppSettings.ZHIProjectConfigs;
import com.google.gson.JsonParseException;
import com.collect.senegal.zhiGlobal.zhiAppSettings.ZHIProjectRouter;
import com.collect.senegal.zhiGlobal.zhiHandler.ZHIProgressHUDHelper;
import com.collect.senegal.zhiNetApi.ZHIHttpResponse;
import com.collect.senegal.zhiScene.zhiWidget.zhiDialog.ZHIDialogMessage;
import com.collect.senegal.zhiUtils.NetWorkUtil;
import com.collect.senegal.zhiUtils.ToastUtil;

import org.json.JSONException;

import java.net.ConnectException;
import java.net.SocketTimeoutException;
import java.net.UnknownHostException;

import io.reactivex.Observer;
import io.reactivex.disposables.Disposable;
import retrofit2.HttpException;

public abstract class BaseSubscriber<T extends ZHIHttpResponse> implements Observer<ZHIHttpResponse>, ZHIProgressHUDHelper.OnFTProgressHUDCancelListener {

    private BasePresenter mBasePresenter;

    private ZHIProgressHUDHelper mZHIProgressHUDHelper;

    private Context context;

    private Disposable disposable;

    public static final int RESPONSE_OK_ORI = 0;
    public static final int RESPONSE_OK = 200;
    public static final int RESPONSE_LOGIN = 402;
    public static final int RESPONSE_UPDATE = 999;
    public static final int RESPONSE_EXCEPTION = 400;
    public static final String RESPONSE_OK_OCR = "SUCCESS";
    public static final String RESPONSE_NOT_USER = MyApplication.getAppContext().getString(R.string.user_does_not_exist);
    public static final String RESPONSE_NOT_LOGIN = "8888";
    public static final String RESPONSE_MULTI_LOGIN = "8889";
    public static final String RESPONSE_NOT_FACE = "9999";

    public BaseSubscriber(BasePresenter basePresenter) {
        this(basePresenter, false);
    }

    public BaseSubscriber(BasePresenter basePresenter, boolean isShowLoading) {

        this.mBasePresenter = basePresenter;
        this.context = context;

        BaseContract.View view = this.mBasePresenter.getView();
//        if (view instanceof Fragment) {
//            context = ((Fragment) this.mBasePresenter.getView()).getActivity();
//        } else if (view instanceof Activity) {
//            context = (Activity) view;
//        } else if (view instanceof BaseActivity) {
//            context = (BaseActivity) view;
//        }

        if (isShowLoading) {
            mZHIProgressHUDHelper = new ZHIProgressHUDHelper(context, this, false);
        }
    }

    public BaseSubscriber(Context context, BasePresenter basePresenter, boolean isShowLoading) {

        this.mBasePresenter = basePresenter;
        this.context = context;

//        if (this.mBasePresenter.getView() instanceof Fragment) {
//            context = ((Fragment) this.mBasePresenter.getView()).getActivity();
//        } else if (this.mBasePresenter.getView() instanceof Activity) {
//            context = (Activity) this.mBasePresenter.getView();
//        } else if (this.mBasePresenter.getView() instanceof BaseActivity) {
//            context = (BaseActivity) this.mBasePresenter.getView();
//        }

        if (isShowLoading) {
            mZHIProgressHUDHelper = new ZHIProgressHUDHelper(context, this, false);
        }
    }

    public BaseSubscriber(Context context, boolean isShowLoading) {
        this.context = context;
        if (isShowLoading) {
            mZHIProgressHUDHelper = new ZHIProgressHUDHelper(context, this, false);
        }
    }

    @Override
    public void onSubscribe(Disposable d) {
        showProgressHUD();
    }

    @Override
    public void onError(Throwable e) {
        e.printStackTrace();
        dismissProgressHUD();
        if (e instanceof HttpException) {//对网络异常 弹出相应的toast
            HttpException httpException = (HttpException) e;
            if (TextUtils.isEmpty(httpException.getMessage())) {
                ToastUtil.s(MyApplication.getAppContext().getString(R.string.network_anomaly));
            } else {
                String errorMsg = httpException.getMessage();
                if (TextUtils.isEmpty(errorMsg)) {
                    ToastUtil.s(MyApplication.getAppContext().getString(R.string.network_anomaly));
                } else {
                    ToastUtil.s(errorMsg);
                }
            }
        } else if (e instanceof JsonParseException
                || e instanceof JSONException
                || e instanceof ParseException) {//解析异常
            ToastUtil.s(MyApplication.getAppContext().getString(R.string.data_exception));
        } else if (e instanceof UnknownHostException) {
            ToastUtil.s(MyApplication.getAppContext().getString(R.string.connection_failed));
        } else if (e instanceof SocketTimeoutException) {
            ToastUtil.s(MyApplication.getAppContext().getString(R.string.request_timed_out));
        } else if (e instanceof ConnectException) {
            ToastUtil.s(MyApplication.getAppContext().getString(R.string.connection_failed));
        } else {//未知错误
            if (NetWorkUtil.isNetworkConnected(context)) {
                ToastUtil.s(MyApplication.getAppContext().getString(R.string.network_error));
            } else {
                ToastUtil.s(MyApplication.getAppContext().getString(R.string.disconnected_from_the_network));
            }
        }
        onHttpError(RESPONSE_EXCEPTION, MyApplication.getAppContext().getString(R.string.network_anomaly));
    }


    @Override
    public void onNext(ZHIHttpResponse httpResponse) {
        dismissProgressHUD();
        Log.d("TAG", "onNext: " + httpResponse.code + "");
        //解析 httpResponse
        if (httpResponse.code == RESPONSE_OK || httpResponse.code == RESPONSE_OK_ORI) {
            onSuccess(httpResponse.obj);
        } else if ((httpResponse.code + "").equalsIgnoreCase(RESPONSE_NOT_LOGIN)) {
            //未登录
            ToastUtil.s(httpResponse.code + " " + MyApplication.getAppContext().getString(R.string.please_login_again));
            ZHIProjectRouter.toRegLoginV2();

        } else if ((httpResponse.code + "").equalsIgnoreCase(RESPONSE_MULTI_LOGIN)) {
            //未登录
            if (context != null) {
                ZHIDialogMessage.showDialog(
                        context,
                        MyApplication.getAppContext().getString(R.string.warning),
                        MyApplication.getAppContext().getString(R.string.your_account_is_logged_in_elsewhere_is_your),
                        MyApplication.getAppContext().getString(R.string.no),
                        MyApplication.getAppContext().getString(R.string.yes),
                        tag -> {
                            ZHIProjectRouter.toRegLoginV2();
                        });
            } else {
                ZHIProjectRouter.toRegLoginV2();
            }
        } else if ((httpResponse.code + "").equalsIgnoreCase(RESPONSE_NOT_FACE)) {
            //未登录
            if (ZHIProjectConfigs.OPEN_FACE_DETECT) {
                ZHIProjectRouter.toRegFaceV2();
            } else {
                onSuccess(httpResponse.obj);
            }
        } else if ((httpResponse.code + "").equalsIgnoreCase(RESPONSE_OK_OCR)) {
            //第三方识别返回
            onSuccess(httpResponse.obj);
        } else if (httpResponse.code == RESPONSE_LOGIN) {
            //未登录
            ToastUtil.s(httpResponse.code + " " + MyApplication.getAppContext().getString(R.string.please_login_again));
            ZHIProjectRouter.toRegLoginV2();
        } else if (httpResponse.code == RESPONSE_UPDATE) {
            ToastUtil.s(MyApplication.getAppContext().getString(R.string.app_needs_to_be_upgraded));
        } else if (httpResponse.msg.equalsIgnoreCase(RESPONSE_NOT_USER)) {
            onHttpError(httpResponse.code, RESPONSE_NOT_USER);
        } else {
            onHttpError(httpResponse.code, httpResponse.msg);
        }
    }

    public void onHttpError(int code, String message) {
        //默认归为onFailure处理，上层可覆盖
        onFailure(code, message);
    }

    protected abstract void onSuccess(Object object);

    protected abstract void onFailure(int code, String messge);

    @Override
    public void onComplete() {
        dismissProgressHUD();
    }

    @Override
    public void onCancelProgress() {
    }

    private void showProgressHUD() {
        if (mZHIProgressHUDHelper != null) {
            mZHIProgressHUDHelper.show();
        }
    }

    private void dismissProgressHUD() {
        if (mZHIProgressHUDHelper != null) {
            mZHIProgressHUDHelper.hide();
            mZHIProgressHUDHelper = null;
        }
    }
}